﻿using System.Windows;
using Microsoft.Lync.Model;
using Microsoft.Lync.Model.Group;
using System.Diagnostics;
using System;
using System.Collections.Generic;


namespace SkypeSync
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class SSGroups : Window
    {
        LyncClient _LyncClient;
        private Dictionary<string, GroupWrapper> _Groups = new Dictionary<string, GroupWrapper>();

        public SSGroups()
        {
            InitializeComponent();
        }

        /// <summary>
        /// Adds a new custom group to the signed in user's contact list
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void AddGroup_Button_Click_1(object sender, RoutedEventArgs e)
        {
            if (GroupName_textbox.Text.Length > 0)
            {
                _LyncClient.ContactManager.BeginAddGroup(
                    GroupName_textbox.Text, 
                    (ar) => 
                    {
                        try
                        {
                            _LyncClient.ContactManager.EndAddGroup(ar);
                        }
                        catch (LyncClientException lce) 
                        {
                            Debug.WriteLine(
                                "Lync client exception on add group: " + 
                                lce.Message); 
                        }
                    },
                    null);
                GroupName_textbox.Text = string.Empty;
            }

        }

        private void RemoveGroup_Button_Click_1(object sender, RoutedEventArgs e)
        {
            if (GroupList_ListBox.SelectedItem == null)
            {
                return;
            }
            try
            {
                GroupWrapper groupToRemove;
                if (_Groups.TryGetValue(GroupList_ListBox.SelectedItem.ToString(), out groupToRemove))
                {
                    _LyncClient.ContactManager.BeginRemoveGroup(
                        groupToRemove.LyncGroup,
                        (ar) =>
                        {
                            try
                            {
                                _LyncClient.ContactManager.EndRemoveGroup(ar);
                            }
                            catch (LyncClientException lce) 
                            {
                                Debug.WriteLine(
                                    "Lync client exception on remove group: " + lce.Message); 
                            }
                        },
                        null);

                }
                else
                {
                    Debug.WriteLine(
                        GroupList_ListBox.SelectedItem.ToString() + 
                        " was not found in the dictionary");
                }

            }
            catch (InvalidOperationException)
            {
                Debug.WriteLine(
                    "Invalid operation in RemoveGroup_Button_Click1"); 
            }

        }

        private void RenameGroup_Button_Click_1(object sender, RoutedEventArgs e)
        {
            if (GroupList_ListBox.SelectedItem == null || GroupName_textbox.Text.Length < 1)
            {
                return;
            }

            GroupWrapper groupToRename;
            if (_Groups.TryGetValue(GroupList_ListBox.SelectedItem.ToString(), out groupToRename))
            {
                //Rename a Group after casting to CustomGroup
                ((CustomGroup)groupToRename.LyncGroup).BeginRename(
                    GroupName_textbox.Text,
                    (ar) =>
                    {
                        try
                        {
                            ((CustomGroup)groupToRename.LyncGroup).EndRename(ar);
                        }
                        catch (LyncClientException lce) 
                        {
                            Debug.WriteLine(
                                "Lync client exception on rename group: " + 
                                lce.Message); 
                        };
                    },
                    null);

                GroupName_textbox.Text = string.Empty;
            }
            else
            {
                Debug.WriteLine(
                    GroupList_ListBox.SelectedItem.ToString() + 
                    " was not found in the dictionary");
            }

        }

        private void Window_Loaded_1(object sender, RoutedEventArgs e)
        {
            //GroupList_ListBox
            try 
            {
                _LyncClient = LyncClient.GetClient();
                _LyncClient.ContactManager.GroupAdded += ContactManager_GroupAdded;
                _LyncClient.ContactManager.GroupRemoved += ContactManager_GroupRemoved;
                LoadList();
            }
            catch (LyncClientException lce) 
            {
                Debug.WriteLine(
                    "Lync client exception on GetClient() in Window Loaded " + 
                    lce.Message);
            }

        }

        /// <summary>
        /// Loads a list box with existing contact list groups
        /// by iterating on the Groups collection of the ContactManager 
        /// property on LyncClient.
        /// </summary>
        private void LoadList()
        {
            GroupList_ListBox.Items.Clear();
            foreach (Group group in _LyncClient.ContactManager.Groups)
            {
                //The Group is wrapped in a custom class to allow
                //override of ToString() method
                GroupWrapper gWrap = new GroupWrapper(group);

                //GroupWrapper class registers for the Group.NameChanged
                //event and bubbles event to UI layer so the 
                //listbox gets reloaded with new name
                gWrap.NameChanged += gWrap_NameChanged;

                GroupList_ListBox.Items.Add(gWrap);
                if (_Groups.ContainsKey(group.Name))
                {
                    continue;
                }

                //Dictionary of GroupWrapper objects with group name as key
                _Groups.Add(group.Name, gWrap);
            }
        }
        void ContactManager_GroupRemoved(object sender, GroupCollectionChangedEventArgs e)
        {
            this.Dispatcher.Invoke(new DelegatedMethod(RemoveGroupFromList), new object[] {e.Group});
        }

        void ContactManager_GroupAdded(object sender, GroupCollectionChangedEventArgs e)
        {
            this.Dispatcher.Invoke(new DelegatedMethod(AddGroupToList), new object[] { e.Group });
        }

        private delegate void DelegateNoParams();

        private delegate void DelegatedMethod(Group group);

        private void RemoveGroupFromList(Group group)
        {
                GroupWrapper groupToRemove;
                if (_Groups.TryGetValue(group.Name, out groupToRemove))
                {
                    if (GroupList_ListBox.Items.Contains(groupToRemove))
                    {
                        GroupList_ListBox.Items.Remove(groupToRemove);
                        _Groups.Remove(group.Name);
                    }
                    else
                    {
                        Debug.WriteLine(group.Name + " was not found in list");
                    }
                }

        }

        private void AddGroupToList(Group group)
        {
            if (!GroupList_ListBox.Items.Contains(group.Name))
            {
                GroupWrapper gWrap = new GroupWrapper(group);
                gWrap.NameChanged += gWrap_NameChanged;
                GroupList_ListBox.Items.Add(gWrap);
                _Groups.Add(gWrap.LyncGroup.Name, gWrap);
            }
        }

        void gWrap_NameChanged(string oldName, string newName)
        {
            this.Dispatcher.Invoke(new DelegateNoParams(LoadList));
        }

        private void ManageContats_Button_Click_1(object sender, RoutedEventArgs e)
        {
            SSContacts contactWindow = new SSContacts();
            App.Current.MainWindow = contactWindow;
            this.Close();
            contactWindow.Show();
        }
    }
}
